Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

CIP-00xx | On-Chain Token Owner Key Registration #118

Closed

Conversation

KtorZ
Copy link
Member

@KtorZ KtorZ commented Aug 17, 2021

Abstract

This specification defines a new transaction metadata label (i.e. 178) and entry for CIP-0010 to associate some arbitrary keys to some assets during a minting transaction.

Motivation

CIP-0026 highlights several mechanisms by which a metadata owner may want to associate its data to a particular on-chain event. We consider here the use-case of token minting, for which the relation between an owner (hereby represented by some cryptographic public key) and the metadata is unclear, in particular in the context of minting policies based on phase-2 (a.k.a Plutus) scripts. This proposal makes of the transaction metadata AND, a minting transaction to create this relationship between the owner and the on-chain event corresponding to the token minting.

Specification

Applications minting tokens on the Cardano blockchain may choose to associate the following transaction metadata to facilitate association of off-chain metadata with the corresponding on-chain event. When doing so, the transaction metadata MUST be included in the same transaction minting (or burning) the assets referenced in the metadata.

NOTE

The following specification is also provided in annexe as a standalone .cddl file.

METADATA-ENTRY =
  { 178: METADATUM }

METADATUM =
  { * POLICY-ID => (  (0, KEY-HASH) 
                   // (1, { * ASSET-NAME => * KEY-HASH })
                   )
  }

ASSET-NAME =
  bytes .size (0..32)

KEY-HASH =
  bytes .size 28

When discovering such a on-chain metadata entry, client application MUST verify that the policy and (when applicable) assets referenced in the metadata are present in the transaction. Then, they MAY automatically trust any off-chain metadata entry signed by one of the private registered counterpart, according to CIP-0026.

Rationale

  • Ensuring the metadata is included as part of the minting (or burning) transaction ensures that it is also automatically signed by the token issuer.
  • We only associate certain assets to key hashes, so that we keep the on-chain data rather small and favor off-chain solution for metadata, which can now be authenticated with the registered keys.
  • The specification allows for defining one key per asset or, a key for an entire policy. The latter is likely the most common use-case as we expect a token issuer to use a single key to authenticate all its token metadata.

Backwards Compatibility

N/A

Reference Implementation(s)

N/A

Copyright

CC-BY-4.0

bytes .size 28
```

When discovering such a on-chain metadata entry, client application MUST verify that the policy and (when applicable) assets referenced in the metadata are present in the transaction. Then, they MAY automatically trust any off-chain metadata entry signed by one of the private registered counterpart, according to [CIP-0026].
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Consider the example of TributeCoin. The minting policy for TributeCoin says that anyone can forge it so long as they send me (Michael Peyton Jones) X Ada for each coin that they mint.

Now, if I understand this scheme correctly, any person who mints TributeCoin could also include transaction metadata indicating that their keys should be associated with the asset id. This could lead to them squatting on the metadata, or it might lead to multiple registrations if the true owner (or other bystanders!) submitted more registrations.

So at the least I think this CIP needs a proposal for what to do in case of multiple registrations. A simple solution would be to privilege the first such registration; but this then introduces incentives for front-running such transactions in order to squat metadata.

The underlying issue is that it is just not true that the party who mints the tokens is also the party who "owns" the tokens (in the social sense of: wrote the script, runs the scheme, agrees to exchange them for things, etc.). So the fact that a transaction mints tokens is not proof that that person has the right to make metadata associations.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well, to a certain extend, if you are able to mint asset A, you effectively are the owner of asset A and being able to set metadata for that asset sounds reasonable. You minted it after all.

Yet, there's an issue w.r.t to keys associated with the policy itself, for which I agree, ownership is generally ambiguous / undefined.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Well, to a certain extend, if you are able to mint asset A, you effectively are the owner of asset A and being able to set metadata for that asset sounds reasonable. You minted it after all.

I don't agree with this at all. You own the token in the sense that you can move it around on the chain, but I think it's a serious confusion to mix that up with the person who should be setting the metadata. Let's call the two parties "the owner" and "the organizer".

Perhaps it would help if I gave a more realistic example. Suppose Alice (the organizer) wants to run an auction. She sets it up so that in order to participate, you have to lock up some collateral at a particular script address, and this lets you (the owner) mint a participation token. All the participation tokens have the same asset id (i.e. are fungible). You can then use the token to register a bid, and at the end Alice completes the auction, taking a fee from the locked funds of each participant, and the entirety if they failed to participate. (Bit of a weird auction, but never mind)

Who should set the metadata for the token? Is it Alice who actually set up the whole thing? Or is it Bob, Carol, Dave, Edna ... who minted participation tokens? I think that any answer other than Alice is clearly wrong, and a system which makes it possible (let alone easy) for Bob, Carol, Dave etc. to do so (or to effectively contest it) is wrong-headed and will dissuade people from running such (sensible) setups because of how easy to abuse they would be.

Yet, there's an issue w.r.t to keys associated with the policy itself, for which I agree, ownership is generally ambiguous / undefined.

No, because people will also mint fungible tokens multiple times. Asset ids absolutely can appear in multiple minting events.


Ultimately, I think this scheme mostly works for NFT drops. I wouldn't object to that if it weren't for the fact that it seems actively harmful for other setups. And we have no way of distinguishing an NFT-drop-like scenario from any others (it's... metadata!), so I'm not sure how we could even limit it to that case.

Copy link
Member Author

@KtorZ KtorZ Oct 18, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I see your point; I still think there's a good bunch of use-cases which can be covered by this approach nonetheless. Perhaps it needs to be "branded" better even though I don't think the proposal currently claims to solve the ownership question by itself. It merely gives one way of linking some keys to some policy, which may turn useful for some use-cases where the minters are also the token metadata owners (and I insist that so far, this has been the most common case).

What do you think of adding a warning / disclaimer that, this particular solution only work under this particular assumption but is probably unfit for other use-cases?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think of adding a warning / disclaimer that, this particular solution only work under this particular assumption but is probably unfit for other use-cases?

So how do I, as the consumer of token metadata, know whether this is a usecase where the metadata can be trusted, or one where it can't?

The issue isn't that it works in one case and can't be used in another case, it's that it in the cases where it doesn't work it's an attack vector, and there's no way for the consumer to distinguish those without... metadata. At which point you have to have established an alternative metadata channel which you might as well use for the rest of it.

It merely gives one way of linking some keys to some policy

But the meaning of that link is unclear without metadata. It could tell you that the link was created by the "organizers", and thus you can trust it. Or it might not. And you can't tell which.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ultimately, the decision to trust a key belongs to the end users. Only the discovery of keys is automated through that CIP. Yet, yes, I agree that it's potentially confusing and could be used in an adversarial way.

Hmm. I originally thought of this as a way for token issuers to leverage the chain to advertise their key. But, it is quite clear now that for this to work, it would be necessary to also clearly communicate that a token is following this CIP; in which case issuers could as well just advertise their public metadata keys.

This is quite unsatisfactory 😔. Alternatively, I imagine we could use a well-defined Plutus policy which would enforce that a token in only minted under some conditions which would render this approach valid. Given that the script hash is known of clients, it would solve the problem.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Only the discovery of keys is automated through that CIP.

Right, but the issue is that "discovery" has to mean something more than "here's a key", it has to say something about that key. A keyserver associates an email address with a key, etc. If we can't make any guarantees about this key... it's not very useful.

Alternatively, I imagine we could use a well-defined Plutus policy which would enforce that a token in only minted under some conditions which would render this approach valid.

All that Plutus scripts do is look at the transaction and check conditions... which is something that the client can perfectly well do themselves! And the thing that you really want to know (what is the minting policy saying?) is something that's opaque to everyone, and Plutus scripts have no privileged access to that.

Having said that, this could work for currencies whose policy is a "native" script, in much the same spirit as what you propose in the off-chain metadata proposal. Of course, that's much less interesting because you can just look at the policy itself, rather than putting something in the metadata and then looking at the policy to check that it's correct...

Copy link
Member Author

@KtorZ KtorZ Oct 19, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All that Plutus scripts do is look at the transaction and check conditions... which is something that the client can perfectly well do themselves!

What I meant is that, you can capture as a Plutus monetary policy the use-case where minter = owner in such a way that the monetary policy is recognizable by clients. That is, if a token is minted according to this particular policy, then CIP-XXXX applies. We can't do this with phase-1 monetary policy because the policy contains the key necessary for minting. With Plutus, you could imagine a policy that leverage the redeemer to define the minter, while keeping the policy itself static.

By fixing the policy, we have more freedom as how to define metadata for this type of policy (but it's also quite limiting since all assets minted under that policy need to share some common behavior). Also, take this with a grain of salt, it's mostly me grooming out loud without any clear design in mind.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What I meant is that, you can capture as a Plutus monetary policy the use-case where minter = owner in such a way that the monetary policy is recognizable by clients. That is, if a token is minted according to this particular policy, then CIP-XXXX applies.

I see. Yes, you could whitelist some monetary policies (configurable by the redeemer, as you point out), such that this CIP would apply. But then you would need to restrict it to metadata about the tokens forged there, since this policy would be shared between all parties making use of this scheme.

@gitmachtl
Copy link
Contributor

I would love to discuss if it would also be possible to extend this method to allow hw-key-based policies to verify there owner/creator-ship. Soon we'll have the feature to have the policy key on a hw-ledger. This is already working but is not released yet for the public. So we have a great security upgrade here for NFTs/NFs. The thing is, you need a signed entry for each parameter in the json file for the offchain metadata registry. But to generate these, we would need additional codespace in the cardano-app on hw wallets like ledger/trezor. Doing a already signed minting/burning transaction onChain with that policyKey could help us out here maybe? Do you have any thoughts on that?

@KtorZ
Copy link
Member Author

KtorZ commented Oct 18, 2021

@gitmachtl I think it works indeed well with policies based on HW keys. In the end, this approach gives you way to "assign" some other keys as legitimate keys for metadata ownership. Thus, you could use hot keys distinct from the HW keys and sign metadata with them.

However, I think there's still many use-cases for signing more than just transactions with a HW device. I am not sure what the implementation plan look like for the HW team but I'd expect that this is something on the radar. Especially since CIP-0008 came out.

@gitmachtl
Copy link
Contributor

@KtorZ the hw team is currently pretty busy and there are no plans to implement the token-registry-metadata signing into the cardano-app. it would need extra code space and also a full gui, check, etc. like the other stuff in cardano-app. so i was looking to find other ways that would only need a signed transaction/metadata onchain to proof the ownership and that this somehow can be used to verify and set the provided token metadata.

@KtorZ KtorZ added the State: Likely Deprecated Close if confirmed deprecated (or long waiting). label Oct 19, 2021
@crptmppt crptmppt changed the title CIP-0028 | On-Chain Token Owner Key Registration CIP-00xx | On-Chain Token Owner Key Registration Dec 2, 2021
@michaelpj
Copy link
Contributor

I thought of a potential way to rescue this. Rather than looking for metadata in a minting/burning transaction, we instead look for metadata in a transaction that strictly precedes any minting or burning transactions for the listed policy ID.

The reason for this is that before any transaction has minted or burned the tokens, the only person who can know that the policy ID (which is a hash!) is interesting is the organizer. So metadata posted in that way must come from the organizer.

The remaining issue I can see is front-running: an attacker can look for transactions of this kind and try and get their own metadata posting in first. I think this is somewhat inevitable, but the consequences are not too bad: the organizer can simply peturb their script (getting a new policy ID), and submit again until they successfully post the metadata first. For this reason I expect this kind of attack would not be profitable enough for attackers to be worth doing, and mostly it would work fine.

@KtorZ KtorZ closed this Jan 11, 2022
@michaelpj michaelpj mentioned this pull request Feb 28, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
State: Likely Deprecated Close if confirmed deprecated (or long waiting).
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants